#
# OSZSNMP
# Copyright (C) 2010 Open Sistemas <imasd@opensistemas.com>
#
# This program is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program. If not, see <http://www.gnu.org/licenses/>.
#
package OpenSistemas::OSZSNMP;

use strict;
use warnings;
use Carp;

use OpenSistemas::OID::Tree;
use OpenSistemas::OID::Item;
use OpenSistemas::Zabbix::Sites;
use OpenSistemas::Zabbix::Hosts;
use OpenSistemas::Zabbix::Alarms;

use NetSNMP::agent (':all');

our $VERSION = "1.0";

sub new
{
  my $pkg = shift;

  croak 'Missing parameter, agent name' if !@_;
  my $agentName = shift;

  my $self = {
    agentName => $agentName,
    agent => undef,
    baseOID => '.1.3.6.1.4.1.35633',
    sites => undef,
    hosts => undef,
    alarms => undef,
    tree => undef,
    pollTime => 60,
    polling => 0,
    dbh => undef,
    end => 0
  };

  bless $self, $pkg;
  return $self;
}

sub registerAgent
{
  my $self = shift;

  croak 'Missing parameter, handler' if !@_;
  my $hnd = shift;

  $self->{agent} = new NetSNMP::agent('Name' => $self->{agentName}, 'AgentX' => 1);
  $self->{agent}->register($self->{agentName}, new NetSNMP::OID($self->{baseOID}), $hnd);
}

sub disconnectAgent
{
  my $self = shift;

  $self->{agent}->shutdown();
}

sub connection
{
  my $self = shift;

  croak 'Missing parameter' if !@_;

  $self->{dbh} = shift;
}

sub disconnect
{
  my $self = shift;

  croak 'No open connection' if !$self->{dbh};

  $self->{dbh}->disconnect();
}

sub update
{
  my $self = shift;

  croak 'No database connetion' if !$self->{dbh};

  if(!$self->{sites})
  {
    $self->{sites} = OpenSistemas::Zabbix::Sites->new(dbh => $self->{dbh}, baseOID => $self->{baseOID});
  }
  if(!$self->{hosts})
  {
    $self->{hosts} = OpenSistemas::Zabbix::Hosts->new(dbh => $self->{dbh}, baseOID => $self->{baseOID});
  }
  if(!$self->{alarms})
  {
    $self->{alarms} = OpenSistemas::Zabbix::Alarms->new(dbh => $self->{dbh}, baseOID => $self->{baseOID});
  }

  if(!$self->{tree})
  {
    $self->{tree} = OpenSistemas::OID::Tree->new();
    $self->{tree}->sort();
  }

  $self->{sites}->update();
  $self->{hosts}->update();
  $self->{alarms}->update();
}

sub sorted
{
  my $self = shift;

  return $self->{tree}->sorted();
}

sub sort
{
  my $self = shift;

  return $self->{tree}->sort();
}

sub polling
{
  my $self = shift;

  if(@_)
  {
    $self->{polling} = shift;
  }
  else
  {
    return $self->{polling};
  }
}

sub pollTime
{
  my $self = shift;

  if(@_)
  {
    $self->{pollTime} = shift;
  }
  else
  {
    return $self->{pollTime};
  }
}

sub pollTimeAdd
{
  my $self = shift;

  croak 'Missing parameter, seconds to add' if !@_;

  $self->{pollTime} += shift;
}

sub getItem
{
  my $self = shift;

  croak 'Missing parameter, OID' if !@_;

  return $self->{tree}->get(shift);
}

sub getNextItem
{
  my $self = shift;

  croak 'Missing parameter, OID' if !@_;

  return $self->{tree}->getnext(shift);
}

sub writableItem
{
  my $self = shift;

  croak 'Missing parameter, OID' if !@_;

  return $self->{tree}->writable(shift);
}

sub setItem
{
  my ($self, $item) = @_;

  croak 'OIDTree: no item to store' if !$item;

  $self->{tree}->set($item);
}

sub end
{
  my $self = shift;

  $self->{end} = 1;
}

sub running
{
  my $self = shift;

  return $self->{end} == 0;
}

sub loop
{
  my $self = shift;

  croak 'Tried to loop, but the agent is not registered' if !$self->{agent};

  $self->{agent}->agent_check_and_process(1);
}

1;
